<template>
  <div class="file-manager-container">

    <!-- 操作工具栏（替换为组件） -->
    <OperationBar
        :isDisabled="pathStack.length === 0"
        :isRecycle="true"
        @go-back="goBack"
        @upload="handleUpload"
    />

    <!-- 百度网盘风格的文件网格 -->
    <el-row :gutter="20" class="file-grid">
      <!-- 文件项（替换为组件） -->
      <el-col
          v-for="(row, index) in filteredFiles"
          :key="row.fileId"
          :xs="12" :sm="8" :md="6" :lg="4"
          class="file-grid-item"
      >
        <FileItem
            :file="row"
            @open="handleFileOpen"
            @download="handleDownload"
            @share="handleShare"
            @delete="handleDelete"
            @edit="handleEdit"
        />
      </el-col>
      <!-- 新增的空网格项，该网格用于新建文件夹 -->
<!--      <el-col-->
<!--          :xs="12" :sm="8" :md="6" :lg="4"-->
<!--          class="file-grid-item"-->
<!--      >-->
<!--        <div class="file-card empty-grid">-->
<!--          <div class="file-card-body">-->
<!--            <div class="file-name" style="color: #909399; text-align: center;">-->
<!--              <CreateFolder :pathStack="pathStack" @folder-created="loadFiles"/>-->
<!--            </div>-->
<!--          </div>-->
<!--        </div>-->
<!--      </el-col>-->
    </el-row>

    <!-- 文件上传对话框 -->
    <el-upload
        v-model:file-list="fileList"
        :action="uploadUrl"
        :multiple="true"
        :show-file-list="false"
        :before-upload="beforeFileUpload"
        :on-success="handleUploadSuccess"
        style="display: none"
    >
      <template #trigger>
        <div ref="uploadTrigger"></div>
      </template>
    </el-upload>

    <!-- 分页组件 -->
    <div class="pagination-container">
      <CustomPagination
          v-model:current-page="currentPage"
          v-model:page-size="pageSize"
          :total="total"
          @page-change="loadFiles"
      />
    </div>
  </div>
</template>

<script setup>
import {computed, onMounted, ref} from 'vue'
import {ElMessage, ElMessageBox} from 'element-plus'
import {loadFilesApi, updateDocumentApi, downloadFromHDFSApi} from '@/utils/API/file-core/Index.js'
import {hideLoading, showLoading} from "@/utils/LoadingUtil";
import { validateFileName } from '@/utils/validate.js'
import {createNewFileShareLinkApi} from "@/utils/API/file-share";  // 新增导入

// 文件数据
const fileList = ref([])
const searchQuery = ref('')
const currentPage = ref(1)
const pageSize = ref(10)
const total = ref(0)
// 目录管理
const currentDirectoryId = ref(null)
const pathStack = ref([])

// 加载文件数据
const loadFiles = async () => {
  try {
    showLoading()
    const response = await loadFilesApi({
      filePath: "all",
      current: currentPage.value,
      size: pageSize.value,
      status: 1,
      fileType: "video",
    })

    if (response.code === 200) {
      fileList.value = response.data.records
      total.value = response.data.records.length
    }
  } catch (error) {
    ElMessage.error('文件加载失败：' + error.message)
  } finally {
    hideLoading()
  }
}

// 文件过滤
const filteredFiles = computed(() => {
  return fileList.value.filter(file =>
      file.fileName.toLowerCase().includes(searchQuery.value.toLowerCase())
  )
})

// 文件上传处理
const uploadUrl = import.meta.env.VITE_BASE_URL + "/files/upload"
const beforeFileUpload = (file) => {
  const maxSize = 1024 * 1024 * 200 // 100MB
  if (file.size > maxSize) {
    ElMessage.error('文件大小不能超过200MB')
    return false
  }
  return true
}

// 上传成功回调
const handleUploadSuccess = (response) => {
  if (response.code === 200) {
    ElMessage.success(response.msg)
    fileList.value.unshift(response.data)
  }
}

// 文件操作
const handleUpload = () => {
  document.querySelector('.el-upload__input').click()
}

// 面包屑封装成字符串
const filteredBreadcrumb = () => {
  // 根目录返回空字符串（根据后端需求可能需要调整为 '/'，可根据实际接口要求修改）
  if (pathStack.value.length === 0) return '/';
  // 非根目录提取每个目录的fileName并用斜杠连接（原pathStack存储对象数组）
  const pathNames = pathStack.value.map(dir => dir.fileId);
  return '/' + pathNames.join('/') + '/';
}

// 打开文件
const handleFileOpen = (file) => {
  if (file.fileType === "folder") {
    // 改为存储包含 fileName 和 fileId 的对象
    pathStack.value.push({ fileName: file.fileName, fileId: file.fileId })
    currentDirectoryId.value = file.fileId
    currentPage.value = 1
    loadFiles()
  } else {
    // TODO 对文件做预览或者下载
    console.log('打开底层文件:', file.fileName)
  }
}

const goBack = () => {
  if (pathStack.value.length > 0) {
    // 面包屑用路径来表示，先进后出
    pathStack.value.pop()
    const prevDir = pathStack.value[pathStack.value.length - 1]
    currentDirectoryId.value = prevDir ? prevDir.fileId : null
    currentPage.value = 1
    loadFiles()
  } else {
    ElMessage.info('已到达根目录')
  }
}

// 下载文件函数
const handleDownload = (file) => {
  try {
    showLoading()
    downloadFromHDFSApi(file.fileId,file.fileName)
  } catch (e) {
    ElMessage.error("文件下载错误" || e)
  } finally {
    hideLoading()
  }
}

// 删除文件操作
const handleDelete = async (file) => {
  try {
    // 添加删除确认对话框
    await ElMessageBox.confirm(
        `确定要删除文件「${file.fileName}」吗？`,
        '警告操作',
        {
          confirmButtonText: '确认删除',
          cancelButtonText: '取消',
          type: 'warning',
        }
    )

    const response = await updateDocumentApi({
      fileId: file.fileId,
      status: 0  // 切换删除状态
    })

    if (response.code === 200) {
      ElMessage.success(response.msg)
      await loadFiles() // 重新加载数据
    } else {
      ElMessage.error(response.msg || "文件删除失败")
    }
  } catch (error) {
    // 捕获取消操作或接口异常
    if (error !== 'cancel') { // 排除用户主动取消的情况
      ElMessage.error("删除失败：" + error.message)
    }
  }
}

// 修改文件的共享状态
// 修改文件的共享状态
const handleShare = async (file) => {
  try {
    // 第一步：确认操作
    await ElMessageBox.confirm(
        `确定要${file.isShared ? '取消共享' : '共享'}文件「${file.fileName}」吗？`,
        '共享状态修改',
        {
          confirmButtonText: '确认',
          cancelButtonText: '取消',
          type: 'info',
        }
    )

    // 非取消共享时才需要输入参数
    if (!file.isShared) {
      // 第二步：输入共享参数（过期天数和提取码）
      const { value: formData } = await ElMessageBox.prompt(
          `设置「${file.fileName}」的共享参数`,
          '请输入过期天数（数字）和提取码（可选，最多6位）',
          {
            inputPlaceholder: '格式：过期天数,提取码（如：7,123456）',
            inputValidator: (val) => {
              const [days, code] = val.split(',')
              if (!/^\d+$/.test(days)) return '过期天数必须为数字'
              if (code && code.length > 6) return '提取码最多6位'
              return true
            },
            inputValue: '7,' // 默认7天过期
          }
      )

      // 解析输入参数
      const [expireDays, extractCode] = formData.split(',')

      // 第三步：调用共享接口
      const response = await createNewFileShareLinkApi({
        fileId: file.fileId,
        fileName: file.fileName,
        expireDays: Number(expireDays),
        extractCode: extractCode || '', // 提取码可选
        link: file.fileId
      })

      if (response.code === 200) {
        ElMessage.success(`共享成功！链接：${response.data.link} 提取码：${response.data.extractCode}`)
        file.isShared = true // 更新文件共享状态
      } else {
        ElMessage.error(response.msg || '共享失败')
      }
    } else {
      // 取消共享逻辑（需要补充取消共享接口调用）
      ElMessage.warning('取消共享功能待完善，暂不支持')
    }
  } catch (error) {
    if (error !== 'cancel') {
      ElMessage.error('共享操作失败：' + error.message)
    }
  }
}

// 修改文件夹/文件名称
const handleEdit = async (file) => {
  try {
    // 弹出输入对话框
    const { value: newName } = await ElMessageBox.prompt(
        `重命名「${file.fileName}」`,
        '请输入新名称（最多64字符）',  // 更新提示信息
        {
          inputPlaceholder: '请输入新的文件/文件夹名称',
          inputValidator: validateFileName,  // 使用工具函数校验
          inputValue: file.fileName,  // 初始值为原名称
          inputAttrs: { maxlength: 64 }  // 输入框添加长度限制
        }
    )

    // 调用重命名API
    // TODO 此处存在问题，修改文件名称时，需要将文件的所有路径一起修改，否则会出错
    const response = await updateDocumentApi({
      fileId: file.fileId,
      fileName: newName,
    })

    if (response.code === 200) {
      ElMessage.success(response.msg)
      await loadFiles()
    } else {
      ElMessage.error(response.msg || '重命名失败')
    }
  } catch (error) {
    // 捕获取消操作或接口异常
    if (error !== 'cancel') {  // 排除用户主动取消的情况
      ElMessage.error('重命名失败：' + error.message)
    }
  }
}

// 初始化加载
onMounted(() => {
  loadFiles()
})

</script>

<style scoped>
.file-manager-container {
  max-width: 1400px;
  margin: 30px auto;
  padding: 0 30px;
  background-color: #f9f9f9;
  border-radius: 12px;
  box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.05);
}

.breadcrumb {
  margin: 10px 5px;
  font-size: 14px;
  color: #8c939d;
}

.breadcrumb span:hover {
  color: #1890ff;
  cursor: pointer;
}

.operation-bar {
  display: flex;
  align-items: center;
  gap: 16px;
  margin-bottom: 24px;
  padding: 16px 20px;
  background: #fff;
  border-radius: 8px;
  box-shadow: 0 1px 3px rgba(0, 0, 0, 0.08);
}

:deep(.el-table) {
  background: #fff;
  border-radius: 8px;
  box-shadow: 0 1px 6px rgba(0, 0, 0, 0.06);
}

.file-row:hover {
  background-color: #f0f8ff;
  cursor: pointer;
}

.file-item {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 8px 0;
}

.file-icon {
  font-size: 24px;
  color: inherit;
}

.file-name {
  flex: 1;
  font-weight: 500;
  color: #333;
}

.shared-icon {
  color: #66b1ff;
  margin-left: auto;
}

.pagination-container {
  margin-top: 24px;
  text-align: center;
}

.operation-group {
  display: flex;
  gap: 8px;
  justify-content: center;
}

.action-btn {
  display: inline-flex;
  align-items: center;
  padding: 8px 15px;
  border-radius: 6px;
}

@media (max-width: 768px) {
  .file-manager-container {
    padding: 0 15px;
  }

  .operation-bar {
    flex-wrap: wrap;
  }

  .search-input {
    width: 100% !important;
  }
}

/* 完整的悬停变色方案 */
.file-row:hover .file-item {
  color: #1890ff;
}

.file-row:hover .file-icon {
  color: #1890ff !important;
}

.file-row:hover .file-name {
  color: #1890ff !important;
}

.file-grid {
  margin: 20px 0;

  .file-grid-item {
    margin-bottom: 20px;

    .file-card {
      background: #fff;
      border-radius: 8px;
      padding: 16px;
      box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
      transition: all 0.3s;

      &:hover {
        transform: translateY(-3px);
        box-shadow: 0 4px 12px rgba(0, 0, 0, 0.15);
      }

      .file-card-header {
        position: relative;

        .shared-icon {
          position: absolute;
          top: 4px;
          right: 4px;
          font-size: 16px;
          color: #66b1ff;
        }
      }

      .file-card-body {
        margin: 12px 0;

        .file-name {
          font-weight: 500;
          text-align: center;
          @include text-ellipsis;
        }

        .file-meta {
          margin-top: 8px;
          font-size: 12px;
          color: #909399;
          display: flex;
          justify-content: space-between;
        }
      }

      .file-actions {
        display: flex;
        gap: 8px;
        justify-content: center;

        :deep(.file-actions-popover) {
          min-width: 100px;
          padding: 8px 12px;
          border-radius: 6px;
          box-shadow: 0 3px 12px rgba(0, 0, 0, 0.12);
        }

        :deep(.popover-actions) {
          display: flex;
          flex-direction: column;
          gap: 6px;
        }

        :deep(.action-btn) {
          width: 100%;
          justify-content: center;
          padding: 6px 8px;
          transition: all 0.2s;

          &:hover {
            background-color: #f0f8ff;
            border-color: #e6f4ff;
          }
        }
      }
    }
  }
}
</style>


